﻿using System;
using System.Collections.Generic;
using System.Text;

namespace Library.Test.Logic
{
    /// <summary>
    /// Action Func
    /// </summary>
    public class DelegateActionFuncService
    {

        /// <summary>
        /// 执行捕捉异常的带参数的委托
        /// <para>本方法不处理异常，不记录日志也不抛出错误，如果出现异常，则返回指定类型的默认值</para>
        /// </summary>        
        /// <typeparam name="T1">参数1类型</typeparam>
        /// <typeparam name="T2">参数2类型</typeparam>
        /// <typeparam name="T3">参数3类型</typeparam>              
        /// <typeparam name="TResult">返回结果的类型</typeparam>
        /// <param name="action">要调用的委托</param>
        /// <param name="t1">action的参数1</param>
        /// <param name="t2">action的参数2</param>
        /// <param name="t3">action的参数3</param>        
        /// <param name="exceptionHandler">处理异常的handle，默认是null</param>
        /// <returns>委托的返回结果</returns>
        public static TResult Catch<T1,TResult>(T1 t1, Func<T1, TResult> action, Action<Exception> exceptionHandler = null)
        {
            var tResult = default(TResult);
            try
            {
                tResult = action(t1);
            }
            catch (Exception ex)
            {
                exceptionHandler?.Invoke(ex);
            }
            return tResult;
        }



        /// <summary>
        /// 执行捕捉异常的带参数的委托
        /// <para>本方法不处理异常，不记录日志也不抛出错误，如果出现异常，则返回指定类型的默认值</para>
        /// </summary>        
        /// <typeparam name="T1">参数1类型</typeparam>
        /// <typeparam name="T2">参数2类型</typeparam>
        /// <typeparam name="T3">参数3类型</typeparam>              
        /// <typeparam name="TResult">返回结果的类型</typeparam>
        /// <param name="action">要调用的委托</param>
        /// <param name="t1">action的参数1</param>
        /// <param name="t2">action的参数2</param>
        /// <param name="t3">action的参数3</param>        
        /// <param name="exceptionHandler">处理异常的handle，默认是null</param>
        /// <returns>委托的返回结果</returns>
        public static TResult Catch<T1, T2, T3, TResult>(Func<T1, T2, T3, TResult> action, T1 t1, T2 t2, T3 t3, Action<Exception> exceptionHandler = null)
        {
            var tResult = default(TResult);
            try
            {
                tResult = action(t1, t2, t3);
            }
            catch (Exception ex)
            {
                exceptionHandler?.Invoke(ex);
            }
            return tResult;
        }

        /// <summary>
        /// 执行捕捉异常的带参数的委托
        /// <para>本方法不处理异常，不记录日志也不抛出错误，如果出现异常，则返回指定类型的默认值</para>
        /// </summary>        
        /// <typeparam name="T1">参数1类型</typeparam>
        /// <typeparam name="T2">参数2类型</typeparam>
        /// <typeparam name="T3">参数3类型</typeparam>
        /// <typeparam name="T4">参数4类型</typeparam>
        /// <typeparam name="T5">参数5类型</typeparam>        
        /// <typeparam name="T6">参数6类型</typeparam>
        /// <typeparam name="TResult">返回结果的类型</typeparam>
        /// <param name="action">要调用的委托</param>
        /// <param name="t1">action的参数1</param>
        /// <param name="t2">action的参数2</param>
        /// <param name="t3">action的参数3</param>
        /// <param name="t4">action的参数4</param>
        /// <param name="t5">action的参数5</param>
        /// <param name="t6">action的参数6</param>
        /// <param name="exceptionHandler">处理异常的handle，默认是null</param>
        /// <returns>委托的返回结果</returns>
        public static TResult Catch<T1, T2, T3, T4, T5, T6, TResult>(Func<T1, T2, T3, T4, T5, T6, TResult> action, T1 t1, T2 t2, T3 t3, T4 t4, T5 t5, T6 t6, Action<Exception> exceptionHandler = null)
        {
            var tResult = default(TResult);
            try
            {
                tResult = action(t1, t2, t3, t4, t5, t6);
            }
            catch (Exception ex)
            {
                exceptionHandler?.Invoke(ex);
            }
            return tResult;
        }


        /// <summary>
        /// 执行一个无返回值的委托，并用try包裹，如果出错，将会记录异常
        /// <para>本方法将处理异常，作为日志记录，默认采用mongodb，如果mongodb出现异常，则使用NLOG记录在本地，本地的配置请参考NLOG的配置文件</para>
        /// </summary>
        /// <param name="action">要执行的委托</param>
        /// <param name="resoveExceptionAction">自己处理异常的委托</param>
        /// <param name="message">如果出错需要写入的错误描述，默认是“程序出现错误”</param>
        public static void CatchLog(Action action, Action<Exception> resoveExceptionAction = null, string message = "程序出现错误")
        {
            try
            {
                action();
            }
            catch (Exception ex)
            {
                resoveExceptionAction?.Invoke(ex);
            }
        }

        /// <summary>
        /// 执行一个无返回值的委托，并用try包裹，如果出错，将会记录异常
        /// <para>本方法将处理异常，作为日志记录，默认采用mongodb，如果mongodb出现异常，则使用NLOG记录在本地，本地的配置请参考NLOG的配置文件</para>
        /// </summary>
        /// <param name="action">要执行的委托</param>
        /// <param name="resoveExceptionAction">自己处理异常的委托</param>
        /// <param name="message">如果出错需要写入的错误描述，默认是“程序出现错误”</param>
        public static void CatchLog(Action action, Action<Exception> resoveExceptionAction = null)
        {
            try
            {
                action();
            }
            catch (Exception ex)
            {
                resoveExceptionAction?.Invoke(ex);
            }
        }
    }
}
